import { Hono } from "hono";
import { parseEnvs } from "ph-utils/server";
import { serve } from "@hono/node-server";
import { readdir } from "node:fs/promises";
import { fileURLToPath } from "node:url";
import { dirname, join } from "node:path";
import onExit from "./libs/shutdown/index.js";
import { logger } from "hono/logger";
import { create as createLogger, log } from "./libs/logger/index.js";
import { connect, closeAll } from "./libs/mysql/index.js";
import validSignature from "./middlewares/valid_signature.js";
import { bearerAuth } from "hono/bearer-auth";
import { verifyToken } from "./middlewares/index.js";

parseEnvs();

createLogger(process.env.NODE_ENV !== "production" ? "debug" : "info", "app");

const app = new Hono().basePath("/api");

if (process.env.NODE_ENV !== "production") {
  app.use(logger());
}
app.use(
  validSignature({
    ignoreUrls: ["/api/system_monitor"],
  }),
);
app.use(
  "/*/*",
  bearerAuth({
    verifyToken: async (token, c) => {
      const userId = await verifyToken(token);
      if (userId === -1) {
        return false;
      }
      c.set("token", token);
      c.set("userId", userId);
      return true;
    },
  }),
);

/**
 * 动态加载 routes 文件夹里面的路由
 */
async function loadDynamicRoutes() {
  const __filename = fileURLToPath(import.meta.url);
  const __dirname = dirname(__filename);
  const routeFiles = await readdir(join(__dirname, "routes"));
  for (let i = 0, len = routeFiles.length; i < len; i++) {
    const fileName = routeFiles[i];
    const lastDotIndex = fileName.lastIndexOf(".");
    let name = fileName;
    if (lastDotIndex !== -1) {
      name = fileName.substring(0, lastDotIndex);
    }
    const module = await import(`./routes/${name}.js`);
    app.route(name === "index" ? "/" : `/${name}`, module.default);
  }
}

await loadDynamicRoutes();

serve(
  {
    fetch: app.fetch,
    port: Number(process.env.PORT || 3000),
  },
  (info) => {
    // 连接 mysql
    connect({
      urls: [process.env.MYSQL_URL as string],
      logger: process.env.NODE_ENV !== "production",
    });
    log(`Listening on http://${info.address}:${info.port} ...`);
  },
);

onExit(() => {
  closeAll(); // 断开 mysql 连接
  log("shutdown");
});
